<?php
// 订单自主查询系统 - 核心函数库
// 版权所有 © 2025 慕念科技. 保留所有权利.

require_once 'config.php';

/**
 * 获取管理员信息
 * @return array|null 管理员信息
 */
function getAdminInfo() {
    global $pdo;
    
    try {
        $stmt = $pdo->prepare("SELECT id, username, admin_qq FROM admin_users LIMIT 1");
        $stmt->execute();
        return $stmt->fetch(PDO::FETCH_ASSOC);
    } catch (PDOException $e) {
        error_log('获取管理员信息失败: ' . $e->getMessage());
        return null;
    }
}

/**
 * 更新管理员账号密码
 * @param string $username 用户名
 * @param string $password 密码
 * @param string $qq QQ号
 * @return bool 更新结果
 */
function updateAdminInfo($username, $password = null, $qq = null) {
    global $pdo;
    
    try {
        // 准备更新语句
        $sql = "UPDATE admin_users SET username = :username";
        $params = [':username' => $username];
        
        // 如果提供了密码，添加密码更新
        if (!empty($password)) {
            $sql .= ", password = :password";
            $params[':password'] = $password;
        }
        
        // 如果提供了QQ号，添加QQ号更新
        if (!empty($qq)) {
            $sql .= ", admin_qq = :qq";
            $params[':qq'] = $qq;
        }
        
        $sql .= " WHERE id = 1";
        
        $stmt = $pdo->prepare($sql);
        $result = $stmt->execute($params);
        
        // 如果用户名或密码发生变化，清除所有会话
        if ($result && (!empty($username) || !empty($password))) {
            // 在实际生产环境中，这里应该有更完善的会话管理逻辑
            // 这里我们简化处理，只在当前请求中标记会话为无效
            if (session_status() == PHP_SESSION_NONE) {
                session_start();
            }
            
            // 可以在这里实现更复杂的会话失效逻辑
        }
        
        return $result;
    } catch (PDOException $e) {
        error_log('更新管理员信息失败: ' . $e->getMessage());
        return false;
    }
}

/**
 * 查询快递信息
 * @param string $trackingNumber 快递单号
 * @param string $courierCode 快递公司编码（可选）
 * @return array 查询结果
 */
function queryExpress($trackingNumber, $courierCode = null) {
    global $pdo;
    
    // 获取API密钥
    $stmt = $pdo->prepare("SELECT key_value FROM settings WHERE key_name = 'api_key'");
    $stmt->execute();
    $apiKey = $stmt->fetchColumn() ?: '';
    
    if (empty($apiKey)) {
        return ['error' => 'API密钥未设置，请联系管理员'];
    }
    
    // 构建请求参数
    $params = [
        'no' => $trackingNumber
    ];
    
    if (!empty($courierCode)) {
        $params['type'] = $courierCode;
    }
    
    // 发送API请求
    $ch = curl_init();
    curl_setopt($ch, CURLOPT_URL, API_URL . '?' . http_build_query($params));
    curl_setopt($ch, CURLOPT_RETURNTRANSFER, true);
    curl_setopt($ch, CURLOPT_TIMEOUT, 30);
    curl_setopt($ch, CURLOPT_HTTPHEADER, [
        'Authorization: APPCODE ' . $apiKey
    ]);
    
    $response = curl_exec($ch);
    $httpCode = curl_getinfo($ch, CURLINFO_HTTP_CODE);
    
    if (curl_errno($ch)) {
        return ['error' => '请求失败: ' . curl_error($ch)];
    }
    
    curl_close($ch);
    
    // 解析响应
    $result = json_decode($response, true);
    
    if ($httpCode != 200 || !isset($result['result']) || $result['status'] != 0) {
        return ['error' => '查询失败: ' . ($result['msg'] ?? '未知错误')];
    }
    
    return $result;
}

/**
 * 保存查询记录
 * @param string $queryValue 查询值
 * @param string $queryType 查询类型
 * @param array $result 结果数据
 */
function saveQueryRecord($queryValue, $queryType, $result) {
    global $pdo;
    
    $trackingNumber = isset($result['no']) ? $result['no'] : null;
    $courierCode = isset($result['type']) ? $result['type'] : null;
    $resultData = json_encode($result);
    
    $stmt = $pdo->prepare(
        "INSERT INTO express_records (query_value, query_type, tracking_number, courier_code, result_data) 
         VALUES (:query_value, :query_type, :tracking_number, :courier_code, :result_data)"
    );
    
    $stmt->execute([
        ':query_value' => $queryValue,
        ':query_type' => $queryType,
        ':tracking_number' => $trackingNumber,
        ':courier_code' => $courierCode,
        ':result_data' => $resultData
    ]);
}

/**
 * 管理员登录验证
 * @param string $username 用户名
 * @param string $password 密码
 * @return bool 验证结果
 */
function adminLogin($username = null, $password = null) {
    // 检查会话是否已登录
    if (session_status() == PHP_SESSION_NONE) {
        session_start();
    }
    
    if (isset($_SESSION['admin_logged_in']) && $_SESSION['admin_logged_in'] === true) {
        return true;
    }
    
    // 验证登录凭证
    if ($username && $password) {
        global $pdo;
        
        $stmt = $pdo->prepare("SELECT password FROM admin_users WHERE username = :username");
        $stmt->execute([':username' => $username]);
        $dbPassword = $stmt->fetchColumn();
        
        // 支持两种验证方式：
        // 1. password_verify验证加密密码（安装时设置的密码）
        // 2. 直接比较明文密码（手动设置的密码或初始密码）
        if ((password_verify($password, $dbPassword)) || ($dbPassword === $password)) {
            $_SESSION['admin_logged_in'] = true;
            return true;
        }
    }
    
    return false;
}

/**
 * 管理员登出
 */
function adminLogout() {
    if (session_status() == PHP_SESSION_NONE) {
        session_start();
    }
    
    $_SESSION = [];
    
    if (ini_get("session.use_cookies")) {
        $params = session_get_cookie_params();
        setcookie(session_name(), '', time() - 42000,
            $params["path"], $params["domain"],
            $params["secure"], $params["httponly"]
        );
    }
    
    session_destroy();
}

/**
 * 根据查询值获取关联的快递单号
 * @param string $queryValue 查询值
 * @return array 快递单号列表
 */
function getTrackingNumbersByQueryValue($queryValue) {
    global $pdo;
    
    // 查找匹配的收件人信息（姓名、手机号或订单号）
    $stmt = $pdo->prepare("SELECT id FROM recipients WHERE name = ? OR phone = ? OR order_number = ?");
    $stmt->execute([$queryValue, $queryValue, $queryValue]);
    $recipientIds = $stmt->fetchAll(PDO::FETCH_COLUMN);
    
    // 查找匹配的快递单号
    $trackingNumbers = [];
    if (!empty($recipientIds)) {
        $placeholders = implode(',', array_fill(0, count($recipientIds), '?'));
        $stmt = $pdo->prepare("SELECT tracking_number FROM tracking_numbers WHERE recipient_id IN ($placeholders)");
        $stmt->execute($recipientIds);
        $trackingNumbers = $stmt->fetchAll(PDO::FETCH_ASSOC);
    }
    
    // 检查查询值是否直接是快递单号
    $stmt = $pdo->prepare("SELECT tracking_number FROM tracking_numbers WHERE tracking_number = :queryValue");
    $stmt->execute([':queryValue' => $queryValue]);
    $directTrackingNumber = $stmt->fetch(PDO::FETCH_ASSOC);
    
    if ($directTrackingNumber) {
        // 检查是否已在列表中
        $exists = false;
        foreach ($trackingNumbers as $tn) {
            if ($tn['tracking_number'] === $directTrackingNumber['tracking_number']) {
                $exists = true;
                break;
            }
        }
        
        if (!$exists) {
            $trackingNumbers[] = $directTrackingNumber;
        }
    }
    
    return $trackingNumbers;
}

/**
 * 添加收件人信息
 * @param string $name 姓名
 * @param string $phone 手机号
 * @param string $orderNumber 订单号
 * @return int 收件人ID
 */
function addRecipient($name, $phone, $orderNumber = '') {
    global $pdo;
    
    try {
        $stmt = $pdo->prepare("INSERT INTO recipients (name, phone, order_number) VALUES (:name, :phone, :orderNumber)");
        $stmt->execute([':name' => $name, ':phone' => $phone, ':orderNumber' => $orderNumber]);
        return $pdo->lastInsertId();
    } catch (PDOException $e) {
        return 0;
    }
}

/**
 * 获取所有收件人信息
 * @return array 收件人列表
 */
function getAllRecipients() {
    global $pdo;
    
    $stmt = $pdo->prepare("SELECT * FROM recipients ORDER BY created_at DESC");
    $stmt->execute();
    $recipients = $stmt->fetchAll();
    
    // 获取每个收件人的快递单号
    foreach ($recipients as &$recipient) {
        $stmt = $pdo->prepare("SELECT tracking_number FROM tracking_numbers WHERE recipient_id = :id");
        $stmt->execute([':id' => $recipient['id']]);
        $trackingNumbers = $stmt->fetchAll(PDO::FETCH_COLUMN);
        $recipient['tracking_numbers'] = $trackingNumbers;
    }
    
    return $recipients;
}

/**
 * 删除收件人信息
 * @param int $id 收件人ID
 * @return bool 删除结果
 */
function deleteRecipient($id) {
    global $pdo;
    
    try {
        // 开始事务
        $pdo->beginTransaction();
        
        // 先删除相关的快递单号记录
        $stmt = $pdo->prepare("DELETE FROM tracking_numbers WHERE recipient_id = :id");
        $stmt->execute([':id' => $id]);
        
        // 再删除收件人记录
        $stmt = $pdo->prepare("DELETE FROM recipients WHERE id = :id");
        $stmt->execute([':id' => $id]);
        
        // 提交事务
        $pdo->commit();
        return true;
    } catch (PDOException $e) {
        // 发生错误时回滚事务
        $pdo->rollBack();
        return false;
    }
}

/**
 * 添加快递单号
 * @param int $recipientId 收件人ID
 * @param string $trackingNumber 快递单号
 * @return bool 添加结果
 */
function addTrackingNumber($recipientId, $trackingNumber) {
    global $pdo;
    
    try {
        $stmt = $pdo->prepare("INSERT INTO tracking_numbers (recipient_id, tracking_number) VALUES (:recipient_id, :tracking_number)");
        return $stmt->execute([':recipient_id' => $recipientId, ':tracking_number' => $trackingNumber]);
    } catch (PDOException $e) {
        return false;
    }
}

/**
 * 根据收件人ID获取快递单号
 * @param int $recipientId 收件人ID
 * @return array 快递单号列表
 */
function getTrackingNumbersByRecipientId($recipientId) {
    global $pdo;
    
    $stmt = $pdo->prepare("SELECT tracking_number FROM tracking_numbers WHERE recipient_id = :id");
    $stmt->execute([':id' => $recipientId]);
    return $stmt->fetchAll(PDO::FETCH_COLUMN);
}

/**
 * 删除快递单号
 * @param string $trackingNumber 快递单号
 * @return bool 删除结果
 */
function deleteTrackingNumber($trackingNumber) {
    global $pdo;
    
    try {
        $stmt = $pdo->prepare("DELETE FROM tracking_numbers WHERE tracking_number = :tracking_number");
        return $stmt->execute([':tracking_number' => $trackingNumber]);
    } catch (PDOException $e) {
        return false;
    }
}

/**
 * 获取系统设置
 * @return array 系统设置
 */
function getSystemSettings() {
    global $pdo;
    
    $stmt = $pdo->prepare("SELECT key_name, key_value FROM settings");
    $stmt->execute();
    $settings = $stmt->fetchAll();
    
    $result = [];
    foreach ($settings as $setting) {
        $result[$setting['key_name']] = $setting['key_value'];
    }
    
    return $result;
}

/**
 * 根据查询值获取完整的收件人和快递信息
 * @param string $queryValue 查询值（姓名、手机号、订单号或快递单号）
 * @return array 包含收件人和快递信息的数组
 */
function getCompleteTrackingInfoByQuery($queryValue) {
    global $pdo;
    
    $results = [];
    
    // 1. 先通过姓名、手机号或订单号查找收件人
    $stmt = $pdo->prepare("SELECT * FROM recipients WHERE name = ? OR phone = ? OR order_number = ?");
    $stmt->execute([$queryValue, $queryValue, $queryValue]);
    $recipients = $stmt->fetchAll();
    
    // 为每个收件人获取快递单号
    foreach ($recipients as $recipient) {
        $stmt = $pdo->prepare("SELECT tracking_number FROM tracking_numbers WHERE recipient_id = :id");
        $stmt->execute([':id' => $recipient['id']]);
        $trackingNumbers = $stmt->fetchAll(PDO::FETCH_COLUMN);
        
        foreach ($trackingNumbers as $trackingNumber) {
            $results[] = [
                'name' => $recipient['name'],
                'phone' => $recipient['phone'],
                'order_number' => $recipient['order_number'],
                'tracking_number' => $trackingNumber
            ];
        }
    }
    
    // 2. 检查查询值是否直接是快递单号
    $stmt = $pdo->prepare("SELECT tn.tracking_number, r.name, r.phone, r.order_number 
                           FROM tracking_numbers tn 
                           LEFT JOIN recipients r ON tn.recipient_id = r.id 
                           WHERE tn.tracking_number = :queryValue");
    $stmt->execute([':queryValue' => $queryValue]);
    $directInfo = $stmt->fetch(PDO::FETCH_ASSOC);
    
    if ($directInfo) {
        // 检查是否已在结果列表中
        $exists = false;
        foreach ($results as $result) {
            if ($result['tracking_number'] === $directInfo['tracking_number']) {
                $exists = true;
                break;
            }
        }
        
        if (!$exists) {
            $results[] = [
                'name' => $directInfo['name'] ?? '',
                'phone' => $directInfo['phone'] ?? '',
                'order_number' => $directInfo['order_number'] ?? '',
                'tracking_number' => $directInfo['tracking_number']
            ];
        }
    }
    
    return $results;
}

/**
 * 更新系统设置
 * @param string $keyName 设置键名
 * @param string $keyValue 设置值
 * @return bool 更新结果
 */
function updateSystemSetting($keyName, $keyValue) {
    global $pdo;
    
    try {
        // 先尝试更新记录
        $stmt = $pdo->prepare("UPDATE settings SET key_value = :key_value WHERE key_name = :key_name");
        $stmt->execute([':key_name' => $keyName, ':key_value' => $keyValue]);
        
        // 如果没有记录被更新（即记录不存在），则插入新记录
        if ($stmt->rowCount() === 0) {
            $stmt = $pdo->prepare("INSERT INTO settings (key_name, key_value) VALUES (:key_name, :key_value)");
            return $stmt->execute([':key_name' => $keyName, ':key_value' => $keyValue]);
        }
        
        return true;
    } catch (PDOException $e) {
        return false;
    }
}

/**
 * 批量更新系统设置
 * @param array $settings 键值对数组
 * @return bool 更新结果
 */
function batchUpdateSystemSettings($settings) {
    global $pdo;
    
    try {
        $pdo->beginTransaction();
        
        foreach ($settings as $keyName => $keyValue) {
            // 先尝试更新记录
            $stmt = $pdo->prepare("UPDATE settings SET key_value = :key_value WHERE key_name = :key_name");
            $stmt->execute([':key_name' => $keyName, ':key_value' => $keyValue]);
            
            // 如果没有记录被更新（即记录不存在），则插入新记录
            if ($stmt->rowCount() === 0) {
                $stmt = $pdo->prepare("INSERT INTO settings (key_name, key_value) VALUES (:key_name, :key_value)");
                $stmt->execute([':key_name' => $keyName, ':key_value' => $keyValue]);
            }
        }
        
        $pdo->commit();
        return true;
    } catch (PDOException $e) {
        $pdo->rollBack();
        return false;
    }
}

/**
 * 获取单个系统设置值
 * @param string $keyName 设置键名
 * @param mixed $default 默认值
 * @return mixed 设置值或默认值
 */
function getSystemSetting($keyName, $default = null) {
    global $pdo;
    
    try {
        $stmt = $pdo->prepare("SELECT key_value FROM settings WHERE key_name = :key_name");
        $stmt->execute([':key_name' => $keyName]);
        $value = $stmt->fetchColumn();
        
        return $value !== false ? $value : $default;
    } catch (PDOException $e) {
        return $default;
    }
}